unit Unit1;
{$IFDEF FPC}
{$MODE DELPHI}
{$ENDIF}
interface

uses
{$IFNDEF FPC}
  Windows, XpMan,
{$ELSE}
  //LCS, LCL,
{$ENDIF}
  Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls, bass, ComCtrls, ExtCtrls, Menus, utils, tags, adaptors;

type

  { TForm1 }

  TForm1 = class(TForm)
    bplay: TButton;
    bpause: TButton;
    bstop: TButton;
    path: TEdit;
    ADD: TButton;
    playlist: TListBox;
    INFO: TButton;
    REMOVE: TButton;
    OpenFile_: TOpenDialog;
    Timer1: TTimer;
    CheckBox1: TCheckBox;
    volume: TTrackBar;
    Pltm: TTimer;
    Trk: TScrollBar;
    MainMenu1: TMainMenu;
    View: TMenuItem;
    OPEN1: TMenuItem;
    OpenPlaylist1: TMenuItem;
    SavePlaylist1: TMenuItem;
    Label1: TLabel;
    {$IFNDEF FPC}
    XPManifest1: TXPManifest;
    {$ENDIF}
    View1: TMenuItem;
    Equalizer1: TMenuItem;
    procedure FormCreate(Sender: TObject);
    procedure playlistDblClick(Sender: TObject);
    procedure ADDClick(Sender: TObject);
    procedure REMOVEClick(Sender: TObject);
    procedure bstopClick(Sender: TObject);
//    procedure TrkChange(Sender: TObject);
    procedure bpauseClick(Sender: TObject);
    procedure FormClose(Sender: TObject; var Action: TCloseAction);
    procedure Timer1Timer(Sender: TObject);
    procedure bplayClick(Sender: TObject);
    procedure volumeChange(Sender: TObject);
    procedure PltmTimer(Sender: TObject);
//    procedure TrkEnter(Sender: TObject);
    procedure TrkScroll(Sender: TObject; ScrollCode: TScrollCode;
      var ScrollPos: Integer);
    procedure OPEN1Click(Sender: TObject);
    procedure SavePlaylist1Click(Sender: TObject);
    procedure playlistKeyDown(Sender: TObject; var Key: Word;
      Shift: TShiftState);
    procedure OpenPlaylist1Click(Sender: TObject);
    procedure Equalizer1Click(Sender: TObject);

  private
    slide: boolean;
    curlen: Int64;
    _tab: string;
    curlend: Double;
    hstrm :Hstream;
    played: boolean;
    procedure get_tab;
    procedure PlayList_add(const filename: string);
    procedure Play_Begin(const id: Cardinal);
    procedure Play_Disk(const num: longint);
    procedure Play_Stream (Name: string);
    procedure Stop_Stream;
    { Private declarations }
  public
    
    id: Longint;

    { Public declarations }
  end;

var
  Form1: TForm1;
  pl: array[0..255] of PL_Tags;
  fl: array[0..255] of TF_INFO;
  l_size: longint;
implementation
uses Equalizer;
procedure init;
begin
  l_size := 0;
 form1.id := 0;
 bass_init(-1, 44100, 0, 0, nil);
end;
{$IFNDEF FPC}
{$R *.dfm}
{$ELSE}
{$R *.lfm}
{$ENDIF}

procedure Tform1.get_tab;
var
   i: longint;
begin
 _tab := '';
 for i :=1 to 8 do _tab := _tab + ' ';
end;

procedure Tform1.PlayList_add(const filename: string);
var
   info: Ptf_info;
begin

  info := Pl_Add(filename);
  inc(l_size);
  if (info = nil) then exit;
  inc(l_size);
  fl[l_size - 1] := info^;
  pl[l_size - 1] := Unname_Tags(fl[l_size - 1].tags, fl[l_size - 1].filetype);
  playlist.TabOrder:= 20;
 // form1.caption := pl[l_size - 1].title;
  playlist.Items.Append(filename+  _tab + pl[l_size - 1].title);
end;

procedure Tform1.Stop_Stream;
begin
  trk.Enabled := false;
  trk.Position := 0;
  //BASS_STREAMFree(hstrm);
  adaptors.Terminate_Channel(hstrm);
end;

procedure Tform1.Play_Disk(const num: longint);
begin
  //Bass_CdPlay(num, false, true);
end;

procedure Tform1.Play_Begin(const id: CArdinal);
begin
  if (played) then
    Stop_stream;
  trk.Enabled := true;
  played := true;
  path.Text := playlist.Items[id];
  Stop_Stream;
  hstrm := Create_channel(path.Text, false);
  //playlist.Items.;
  label1.Caption := Pl[id].title + ' '+ pl[id].album +' by '+ pl[id].artist;
  curlend := fl[id].length;
  Trk.Max := round(curlend);
  pltm.Enabled := true;
end;

procedure Tform1.Play_Stream(Name: string);
var
  f: pchar;
begin
  f := pchar(name);
  hstrm := BASS_StreamCreateFile(FALSE, f, 0, 0, BASS_MP3_SETPOS);
  if (hstrm <> 0) then
    BASS_channelPlay(hstrm, false);
end;

procedure TForm1.FormCreate(Sender: TObject);
begin
  init;
  get_tab;
  played := true;
  slide := false;
end;

procedure TForm1.playlistDblClick(Sender: TObject);
begin
 Play_begin(playlist.ItemIndex)
end;

procedure TForm1.ADDClick(Sender: TObject);
var
  str: string;
begin
    {str := Open_FIle;
    playlist.Items.Add(str); }
   PlayList_add(Open_File);
   // PlOpen.Execute;
   //Memo1.Lines.add(Plopen.Filter);
end;

procedure TForm1.REMOVEClick(Sender: TObject);
begin
  playlist.items.Delete(playlist.ItemIndex);
end;

procedure TForm1.bstopClick(Sender: TObject);
begin
    Bass_channelStop(hstrm)
end;

procedure TForm1.bpauseClick(Sender: TObject);
begin
  if (played) then
    bass_channelpause(hstrm)
  else
    bass_channelplay(hstrm, false);
  played := not (played);
end;

procedure TForm1.FormClose(Sender: TObject; var Action: TCloseAction);
begin
  STOP_stream;
  ENGINE_FREE;
end;

procedure TForm1.Timer1Timer(Sender: TObject);
begin
  form1.Caption := 'CPU%  ' + FloatToStrF(BASS_GetCPU, ffFixed, 4, 2) + 'time '+
  inttostr(Trk.position div 60) + ':' +inttostr(Trk.position mod 60)  + '//' + inttostr(trk.Max div 60)+ ':' +inttostr(Trk.max mod 60);
end;

procedure TForm1.bplayClick(Sender: TObject);
begin
  Play_begin(id);
end;

procedure TForm1.volumeChange(Sender: TObject);
begin
   bass_channelsetattribute(hstrm, BASS_ATTRIB_MUSIC_VOL_CHAN, volume.Position);
   bass_channelsetattribute(hstrm, BASS_ATTRIB_VOL, volume.Position);
end;

procedure TForm1.PltmTimer(Sender: TObject);
begin
  if (slide) then exit;
  if (Trk.Position < Trk.Max) then
    Trk.Position := round(BASS_ChannelBytes2Seconds(hstrm, BASS_ChannelGetPosition(hstrm, BASS_POS_BYTE)))
  else
  begin
    Stop_Stream;
    trk.Position := 0;
    id := id + 1;
    if (id = (playlist.Count)) then
    begin
      if (Checkbox1.Checked) then
        id := 0
      else
      begin
        pltm.Enabled := false;
        exit;
      end;
    end;
    Play_begin(id);
  end;
end;

procedure TForm1.TrkScroll(Sender: TObject; ScrollCode: TScrollCode;
  var ScrollPos: Integer);
var
  curpos: Int64;
begin
  slide := (ScrollCode <> scEndScroll);
  if (not slide) then
  begin
    curpos := BASS_channelSeconds2Bytes(hstrm, scrollpos);
    bass_channelSetPosition(hstrm, curpos, BASS_POS_BYTE);
    slide := false;
  end;
end;

procedure TForm1.OPEN1Click(Sender: TObject);
begin
  PlayList_add(Open_file);
  //playlist.Items.Add(Open_FIle);
end;

procedure TForm1.SavePlaylist1Click(Sender: TObject);
var
  pl: TstringList;
  i : Cardinal;
begin
  if (playlist.Count = 0) then exit;
  //Save_File(playlist.items);
  pl := TstringList.Create;
  for i := 0 to playlist.Count - 1 do
    pl.Append(playlist.Items[i]);
  Save_File(pl);
  pl.Free;
end;

procedure TForm1.playlistKeyDown(Sender: TObject; var Key: Word;
  Shift: TShiftState);
{$IFDEF FPC}
var
  i: Longint;
{$ENDIF}
begin
  if (key =  46) then
  {$IFNDEF FPC}
    playlist.DeleteSelected;
  {$ELSE}
  begin
    for i := 1 to playlist.count - 1 do
      if (playlist.selected[i]) then playlist.items.delete(i);
  end;
  {$ENDIF}
end;

procedure TForm1.OpenPlaylist1Click(Sender: TObject);
var
  lst: TstringList;
  i: cardinal;
begin
  lst := TstringList.Create;
  lst.LoadFromFile(Open_File);
  for i := 0 to lst.count - 1 do
    playlist.Items.Add(lst.strings[i]);
  lst.Free;
end;

procedure TForm1.Equalizer1Click(Sender: TObject);
begin
  Eq.show;
end;

end.